<?php
// PasswordGen
// Alex McClung
// November, 2007
// Password generator class for generating keyboard-pattern-based or completely random passwords.
// 
// This software is freely distributable under the terms of the GNU General Public License (Version 3).
// For details, see the author's web site: http://www.mcclungalexander.com/
class PasswordGen
{
	//===================================================================================
	// Private Variables
	
	private $keys;                           // Array of Key objects
	private $matrix_file = "key_matrix.txt"; // File to load the key matrix from
	
	//===================================================================================
	// Public Variables
	
	//===================================================================================
	// Public Functions

	//-----------------------------------------------------------------------------------
	// Class constructor
	public function __construct()
	{
		$this->LoadMatrix();
	}
	
	//-----------------------------------------------------------------------------------
	// Generates a keyboard-pattern password
	// $length (int) Character length of the password to generate
	// Returns: string
	public function GeneratePatternedPassword($length)
	{
		$pw = "";
		$key = $this->keys[array_rand($this->keys)];

		for($i=0; $i<$length; $i++)
		{
			$cap = rand(0,1);
			
			if($key != null)
			{
				$key = $key->GetRandomNeighbor();
				$pw .= ($cap == 0) ? $key->value : $key->shift_value;
			}
		}
		return $pw;
	}
	
	//-----------------------------------------------------------------------------------
	// Generates a completely random password
	// $length (int) Character length of the password to generate
	// Returns: string
	public function GenerateRandomPassword($length)
	{
		$pw = "";
		for($i=0; $i<$length; $i++)
		{
			$key = $this->keys[array_rand($this->keys)];
			$pw .= (rand(0,1)==0) ? $key->value : $key->shift_value;
		}
		return $pw;
	}
	
	//===================================================================================
	// Private Functions

	//-----------------------------------------------------------------------------------
	// Loads keyboard mapping from the matrix file
	private function LoadMatrix()
	{
		$this->keys = array();
		$input = file_get_contents(dirname(__FILE__) . DIRECTORY_SEPARATOR . $this->matrix_file);

		$lines = split("\n", $input);
		
		// Loop through the lines once to initialize the keys
		foreach($lines as $line)
		{
			list($value,$neighbors) = split(":", $line);
			$this->keys[$value] = new Key($value);
		}
		
		// Loop through it again so we can add the neighbors to each key
		foreach($lines as $line)
		{
			$line = trim($line);
			// See, here I can just re-use the key objects that have already been instantiated
			// that way, they all have their neigbhors
			list($value,$neighbors) = split(":", $line);

			for($i=0;$i<strlen($neighbors);$i++)
			{
				$c = substr($neighbors,$i,1);
				$this->keys[$value]->AddNeighbor($this->keys[$c]);
			}
		}
	}
}

?>